package com.kexio.dynamic.feature.service;

import com.kexio.dynamic.feature.annotation.FeatureToggle;

import java.util.Map;
import java.util.Set;

/**
 * 功能开关服务接口
 * 
 * 提供功能开关的管理和判断功能
 * 
 * @author Kexio
 * @since 1.0.0
 */
public interface FeatureToggleService {

    /**
     * 检查功能是否启用
     * 
     * @param featureName 功能名称
     * @return 是否启用
     */
    boolean isEnabled(String featureName);

    /**
     * 检查用户的功能是否启用
     * 
     * @param featureName 功能名称
     * @param userId      用户ID
     * @return 是否启用
     */
    boolean isEnabled(String featureName, Long userId);

    /**
     * 检查租户的功能是否启用
     * 
     * @param featureName 功能名称
     * @param tenantId    租户ID
     * @return 是否启用
     */
    boolean isEnabledForTenant(String featureName, Long tenantId);

    /**
     * 检查功能开关（带上下文）
     * 
     * @param featureName 功能名称
     * @param context     上下文参数
     * @return 是否启用
     */
    boolean isEnabled(String featureName, Map<String, Object> context);

    /**
     * 启用功能
     * 
     * @param featureName 功能名称
     */
    void enableFeature(String featureName);

    /**
     * 禁用功能
     * 
     * @param featureName 功能名称
     */
    void disableFeature(String featureName);

    /**
     * 为用户设置功能开关
     * 
     * @param featureName 功能名称
     * @param userId      用户ID
     * @param enabled     是否启用
     */
    void setFeatureForUser(String featureName, Long userId, boolean enabled);

    /**
     * 为租户设置功能开关
     * 
     * @param featureName 功能名称
     * @param tenantId    租户ID
     * @param enabled     是否启用
     */
    void setFeatureForTenant(String featureName, Long tenantId, boolean enabled);

    /**
     * 批量设置功能开关
     * 
     * @param features 功能开关映射 (featureName -> enabled)
     */
    void setFeatures(Map<String, Boolean> features);

    /**
     * 获取所有启用的功能
     * 
     * @return 启用的功能名称集合
     */
    Set<String> getEnabledFeatures();

    /**
     * 获取用户启用的功能
     * 
     * @param userId 用户ID
     * @return 启用的功能名称集合
     */
    Set<String> getEnabledFeatures(Long userId);

    /**
     * 获取租户启用的功能
     * 
     * @param tenantId 租户ID
     * @return 启用的功能名称集合
     */
    Set<String> getEnabledFeaturesForTenant(Long tenantId);

    /**
     * 获取所有功能开关状态
     * 
     * @return 功能开关状态映射
     */
    Map<String, Boolean> getAllFeatureStates();

    /**
     * 检查功能是否存在
     * 
     * @param featureName 功能名称
     * @return 是否存在
     */
    boolean featureExists(String featureName);

    /**
     * 添加功能开关
     * 
     * @param featureName 功能名称
     * @param enabled     初始状态
     */
    void addFeature(String featureName, boolean enabled);

    /**
     * 删除功能开关
     * 
     * @param featureName 功能名称
     */
    void removeFeature(String featureName);

    /**
     * 设置功能开关的百分比（灰度发布）
     * 
     * @param featureName 功能名称
     * @param percentage  百分比 (0-100)
     */
    void setFeaturePercentage(String featureName, int percentage);

    /**
     * 获取功能开关的百分比
     * 
     * @param featureName 功能名称
     * @return 百分比
     */
    int getFeaturePercentage(String featureName);

    /**
     * 添加用户到白名单
     * 
     * @param featureName 功能名称
     * @param userId      用户ID
     */
    void addUserToWhitelist(String featureName, Long userId);

    /**
     * 从白名单移除用户
     * 
     * @param featureName 功能名称
     * @param userId      用户ID
     */
    void removeUserFromWhitelist(String featureName, Long userId);

    /**
     * 检查用户是否在白名单中
     * 
     * @param featureName 功能名称
     * @param userId      用户ID
     * @return 是否在白名单中
     */
    boolean isUserInWhitelist(String featureName, Long userId);

    /**
     * 获取功能开关的白名单用户
     * 
     * @param featureName 功能名称
     * @return 白名单用户ID集合
     */
    Set<Long> getWhitelistUsers(String featureName);

    /**
     * 刷新功能开关缓存
     * 
     * @param featureName 功能名称，null表示刷新所有
     */
    void refreshCache(String featureName);

    /**
     * 清空功能开关缓存
     */
    void clearCache();

    /**
     * 获取功能开关统计信息
     * 
     * @return 统计信息
     */
    FeatureToggleStats getStats();

    /**
     * 根据策略检查功能开关
     * 
     * @param featureName 功能名称
     * @param strategy    开关策略
     * @param context     上下文参数
     * @return 是否启用
     */
    boolean checkByStrategy(String featureName, FeatureToggle.ToggleStrategy strategy, Map<String, Object> context);

    /**
     * 功能开关统计信息
     */
    class FeatureToggleStats {
        private int totalFeatures;
        private int enabledFeatures;
        private int disabledFeatures;
        private long totalChecks;
        private long cacheHits;
        private long cacheMisses;
        private Map<String, Long> featureUsage;

        // Getters and Setters
        public int getTotalFeatures() { return totalFeatures; }
        public void setTotalFeatures(int totalFeatures) { this.totalFeatures = totalFeatures; }
        
        public int getEnabledFeatures() { return enabledFeatures; }
        public void setEnabledFeatures(int enabledFeatures) { this.enabledFeatures = enabledFeatures; }
        
        public int getDisabledFeatures() { return disabledFeatures; }
        public void setDisabledFeatures(int disabledFeatures) { this.disabledFeatures = disabledFeatures; }
        
        public long getTotalChecks() { return totalChecks; }
        public void setTotalChecks(long totalChecks) { this.totalChecks = totalChecks; }
        
        public long getCacheHits() { return cacheHits; }
        public void setCacheHits(long cacheHits) { this.cacheHits = cacheHits; }
        
        public long getCacheMisses() { return cacheMisses; }
        public void setCacheMisses(long cacheMisses) { this.cacheMisses = cacheMisses; }
        
        public Map<String, Long> getFeatureUsage() { return featureUsage; }
        public void setFeatureUsage(Map<String, Long> featureUsage) { this.featureUsage = featureUsage; }
    }
}
